/*
 * Copyright (c) 1997, 2006, Oracle and/or its affiliates. All rights reserved.
 * ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 */

package java.util;

/**
 * <p>这个类提供了List接口的骨架似的实现，来最小化实现基于顺序访问元素（例如链表）的努力。
 * 对于随机访问元素（例如一个数组），应该优先使用abstractList。
 * 
 * <p>这个类与AbstractList相反，它实现了随机访问的方法
 * get(int index)、set(int index、E e)、add(int index、E e)和remove(int index)
 * 基于列表的ListIterator，而不是相反。（abstractlist是这几个方法抽象，ListIterator基于这几个方法实现）
 * 
 * <p>要实现这个列表，程序员只需要继承这个类，并且实现ListIterator和sieze方法。
 * 对于一个不可修改的列表，程序员仅仅需要实现ListIterator的
 * hasNext、next、hasPrevious、previous和index方法。
 * 
 * <p>对于一个可修改的列表，程序员应该额外实现ListIterator的set方法。
 * 对于可变长度的列表，程序员应该额外实现ListIterator的remove和add方法。
 * 
 * <p>程序员应该通常提供一个无参构造器和集合构造器，根据Collection接口规范的提议。
 * 
 *
 * @author  Josh Bloch
 * @author  Neal Gafter
 * @see Collection
 * @see List
 * @see AbstractList
 * @see AbstractCollection
 * @since 1.2
 */

public abstract class AbstractSequentialList<E> extends AbstractList<E> {
    /**
     * Sole constructor.  (For invocation by subclass constructors, typically
     * implicit.)
     */
    protected AbstractSequentialList() {
    }

    /**
     * 返回列表中指定位置的元素。
     *
     * <p>这个实现，首先得到一个指向index元素的ListIterator（使用listIterator(index)）。
     * 然后，使用ListIterator.next得到这个元素，并返回
     *
     * @throws IndexOutOfBoundsException {@inheritDoc}
     */
    public E get(int index) {
        try {
            return listIterator(index).next();
        } catch (NoSuchElementException exc) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
    }

    /**
     * 用指定元素替代列表中指定位置的元素（可选操作）
     *
     * <p>这个实现首先得到一个指向index元素的ListIterator（使用listIterator(index)）。
     * 然后，使用ListIterator.next得到这个元素，并用ListIterator.set替代它。
     *
     * <p>注意：如果迭代器没有实现set操作，实现会抛出UnsupportedOperationException
     *
     * @throws UnsupportedOperationException {@inheritDoc}
     * @throws ClassCastException            {@inheritDoc}
     * @throws NullPointerException          {@inheritDoc}
     * @throws IllegalArgumentException      {@inheritDoc}
     * @throws IndexOutOfBoundsException     {@inheritDoc}
     */
    public E set(int index, E element) {
        try {
            ListIterator<E> e = listIterator(index);
            E oldVal = e.next();
            //next后set，返回的最后元素替换为指定元素
            e.set(element);
            return oldVal;
        } catch (NoSuchElementException exc) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
    }

    /**
     * 插入指定元素到列表的指定位置。）可选操作）
     * 在这个位置的元素（如果有）和任何后边的元素被移动到右边（将它们的index+1）
     *
     * <p>这个实现首先得到一个指向index元素的ListIterator（使用listIterator(index)）。
     * 然后，使用ListIterator.add插入指定元素。
     *
     * <p>注意：如果迭代器没有实现add操作，实现会抛出UnsupportedOperationException
     *
     * @throws UnsupportedOperationException {@inheritDoc}
     * @throws ClassCastException            {@inheritDoc}
     * @throws NullPointerException          {@inheritDoc}
     * @throws IllegalArgumentException      {@inheritDoc}
     * @throws IndexOutOfBoundsException     {@inheritDoc}
     */
    public void add(int index, E element) {
        try {
            listIterator(index).add(element);
        } catch (NoSuchElementException exc) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
    }

    /**
     * 删除列表中指定位置的元素（可选操作）
     * 移动后面的元素到左边（index-1）。
     * 返回被移除的元素。
     *
     * <p>这个实现首先得到一个指向index元素的ListIterator（使用listIterator(index)）。
     * 然后，使用ListIterator.next得到这个元素，并用ListIterator.remove删除指定元素。
     *
     * <p>注意：如果迭代器没有实现remove操作，实现会抛出UnsupportedOperationException
     *
     * @throws UnsupportedOperationException {@inheritDoc}
     * @throws IndexOutOfBoundsException     {@inheritDoc}
     */
    public E remove(int index) {
        try {
            ListIterator<E> e = listIterator(index);
            E outCast = e.next();
            e.remove();
            return outCast;
        } catch (NoSuchElementException exc) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
    }


    // Bulk Operations

    /**
     * 将指定列表的所有元素加入到这个列表的指定位置，（可选操作）。
     * 在这个位置的元素（如果有）和任何这个元素右边的元素，被移动到右边（增加它们的index）
     * 新的元素出现的顺序为指定集合的迭代器的返回顺序。
     * 当执行操作时，如果修改指定列表，操作的结果未知。
     * （这意味着，如果如果指定列表是这个列表，而且列表是非空的，调用的结果未知）
     *
     * <p>这个实现得到指定集合的迭代器和一个指向index元素的ListIterator（使用listIterator(index)）。
     * 然后，它迭代指定集合，将迭代器获取到的元素，插入到列表，
     * 一次一个，使用ListIterator.add，之后使用Iterator.next（来跳过被加入的元素）
     *
     * <p>注意：这个实现会抛出UnsupportedOperationException，如果ListIterator没有实现add操作。
     *
     * @throws UnsupportedOperationException {@inheritDoc}
     * @throws ClassCastException            {@inheritDoc}
     * @throws NullPointerException          {@inheritDoc}
     * @throws IllegalArgumentException      {@inheritDoc}
     * @throws IndexOutOfBoundsException     {@inheritDoc}
     */
    public boolean addAll(int index, Collection<? extends E> c) {
        try {
            boolean modified = false;
            ListIterator<E> e1 = listIterator(index); //e1 为ListIterator
            Iterator<? extends E> e2 = c.iterator(); //e2 为集合的Iterator
            while (e2.hasNext()) {
                e1.add(e2.next()); //e1加入，e2返回元素，并跳过
                modified = true;
            }
            return modified;
        } catch (NoSuchElementException exc) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
    }


    // Iterators

    /**
     * 返回一个覆盖这个列表所有元素的iterator(以适当的顺序）。<p>
     *
     * 这个实现仅仅返回一个覆盖列表的ListIterator
     *
     * @return an iterator over the elements in this list (in proper sequence)
     */
    public Iterator<E> iterator() {
        return listIterator();
    }

    /**
     * 返回一个覆盖列表中元素的ListIterator（以适当的顺序）
     *
     * @param  index index of first element to be returned from the list
     *         iterator (by a call to the <code>next</code> method)
     * @return a list iterator over the elements in this list (in proper
     *         sequence)
     * @throws IndexOutOfBoundsException {@inheritDoc}
     */
    public abstract ListIterator<E> listIterator(int index);
}
